package BNS.graphs;

import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;

import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;


/** Implements a GUI for the creation of graph layouts.
	*/
public class Creator extends JPanel implements ActionListener, ItemListener {
	private static final long serialVersionUID = 01L;// to suppress warning
	private JPanel controlPanel;
	private JPanel describePanel;
//	private GraphPanel gPanel;
	private LayoutMaker gPanel;
	private Graph graph;
	private JButton scramble, shake, relax, step, next;
	JTextField name;
	JCheckBox stress, random, fixed;
	//private ObjectOutputStream oos;
	
	/** Creates and makes visible a GUI for creating layouts. */
	public Creator() {
		setLayout(new BorderLayout());
		gPanel= new LayoutMaker(this);
		add("Center", gPanel);
		controlPanel= new JPanel();
		add("North", controlPanel);
		describePanel= new JPanel();
		add("South",describePanel);
		
		scramble= new JButton("Scramble");
		shake= new JButton("Shake");
		stress= new JCheckBox("Stress");
		random= new JCheckBox("Random");
		relax= new JButton("Relax");
		step= new JButton("Step");
		controlPanel.add(scramble);	scramble.addActionListener(this);
		controlPanel.add(shake);	shake.addActionListener(this);
		controlPanel.add(stress);	stress.addItemListener(this);
		controlPanel.add(random);	random.addItemListener(this);
		controlPanel.add(step);		step.addActionListener(this);
		controlPanel.add(relax);	relax.addActionListener(this);
		
		describePanel.add(new JLabel("label:"));
		name= new JTextField("name",8);		
		describePanel.add(name);	name.addActionListener(this);
		fixed= new JCheckBox("fixed");
		describePanel.add(fixed);	fixed.addItemListener(this);
		next= new JButton("Next");
		describePanel.add(next);	next.addActionListener(this);
		}
	
	/** installs a given Graph into the existing GUI panel. */
	public void init(Graph gr) { 
		System.err.println("Creator init'ed, graph size "+gr.numNodes());
		stop(); graph= gr; gPanel.init(gr); gPanel.start(); 
		}
	
/*	public void destroy() {
//		remove(gPanel);
//		remove(controlPanel);
//		remove(describePanel);
		dispose();
		}
*/	
	/** Stops the graphPanel's operation. */
	public void stop() { gPanel.stop(); }
	
	/** Determines the semantics of a given action, and calls routines to perform them.	*/
	public void actionPerformed(ActionEvent e) {
		Object src= e.getSource();
		//System.err.println("actionPerformed "+ e);
		if (src==name && gPanel.pick!=null) gPanel.pick.lbl= name.getText();
		if (src==relax) gPanel.runRelax();
		if (src==scramble) gPanel.scramble();
		if (src==shake) gPanel.shake();
		if (src==step) { gPanel.stop(); gPanel.relax(); }
		if (src==next) { synchronized(this){ notify(); } // kicks graphlet loop in GraphPack
			//System.err.println("creator waiting");
			}
		gPanel.repaint();
		}
	
	/** Notifies a JCheckBox that its state has been altered and changes model to match. 
		*/
	public void itemStateChanged(ItemEvent e) {
		Object src= e.getSource();
		boolean on= e.getStateChange()==ItemEvent.SELECTED;
		if (src==stress) gPanel.stress= on;
		else if (src==random) gPanel.random= on;
		else if (src==fixed && gPanel.pick!=null) gPanel.pick.fixed= on;
		gPanel.repaint();
		}
	
	/** Remembers what Node was most recently picked by the user, changes its name */
	public void nodePickChanged(Node n) {
		//System.err.println("nodePickChanged "+ n.lbl +" fixed "+ n.fixed);
		fixed.setSelected(n.fixed);
		name.setText(n.lbl);
		repaint();
		}
	
	/** Generates an example Graph of 5 edges and 5 nodes, just for testing. */
	public static void main(String[] args) {
		JFrame frame= new JFrame("GraphPack Creation");
		frame.setSize(500,500);
		Creator crPanel= new Creator();
		frame.setContentPane(crPanel);
		frame.validate();
		frame.setVisible(true);	// must come BEFORE init, so that getSize() works
		Graph gr= new Graph(5,5);
		Node n1= gr.addNode("n1");
		Node n2= gr.addNode("n2");
		Node n3= gr.addNode("n3");
		gr.addEdge(n1,n2);
		gr.addEdge(n2,n3);
		gr.addEdge(n3,n1);
		crPanel.init(gr);
		}
	
	} // EOClass Creator
